package com.ruoyi.controller;

import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.constant.Constants;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.framework.web.service.TokenService;
import com.ruoyi.service.UserService;
import com.ruoyi.system.service.ISysUserService;
import com.ruoyi.vo.ChatMsg;
import com.ruoyi.vo.ChatUserVo;
import com.ruoyi.vo.ResultVo;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.Jwts;
import lombok.extern.slf4j.Slf4j;
import org.apache.tomcat.util.http.parser.Authorization;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Lazy;
import org.springframework.messaging.MessageHeaders;
import org.springframework.messaging.handler.annotation.DestinationVariable;
import org.springframework.messaging.handler.annotation.Header;
import org.springframework.messaging.handler.annotation.MessageMapping;
import org.springframework.messaging.handler.annotation.Payload;
import org.springframework.messaging.simp.SimpMessagingTemplate;
import org.springframework.messaging.simp.annotation.SubscribeMapping;
import org.springframework.messaging.simp.stomp.StompHeaderAccessor;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RestController;

import java.security.Principal;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * websocket控制器
 */
@Slf4j
@RestController
public class WebSocketController {
    @Autowired
    private SimpMessagingTemplate simpMessagingTemplate;

    @Autowired
    private TokenService tokenService;

    @Autowired
    private ISysUserService userService;

    @PostMapping("/friend/friendList")
    public List<Map<String, Object>> getUsers() {
        List<Map<String, Object>> userList = new ArrayList<>();

        // 创建用户1
        Map<String, Object> user1 = new HashMap<>();
        user1.put("img", "");
        user1.put("name", "大毛");
        user1.put("detail", "我是大毛");
        user1.put("lastMsg", "to do");
        user1.put("id", "1002");
        user1.put("headImg", "@/assets/images/head_portrait1.jpg");

        // 创建用户2
        Map<String, Object> user2 = new HashMap<>();
        user2.put("img", "");
        user2.put("name", "小毛");
        user2.put("detail", "我是小毛");
        user2.put("lastMsg", "dada dw ertgthy j uy");
        user2.put("id", "1003");
        user2.put("headImg", "@/assets/images/head_portrait2.jpg");

        // 创建用户3
        Map<String, Object> user3 = new HashMap<>();
        user3.put("img", "");
        user3.put("name", "小王");
        user3.put("detail", "我是小王");
        user3.put("lastMsg", "大萨达萨达所大大萨达");
        user3.put("id", "1004");
        user3.put("headImg", "@/assets/images/head_portrait3.jpg");

        userList.add(user1);
        userList.add(user2);
        userList.add(user3);

        return userList;
    }

    /**
     * 根据用户id获取聊天用户的信息
     * @return
     */
    @GetMapping("/getChatUserInfo/{id}")
    public ResultVo getUsers(@PathVariable Long id) {
        SysUser sysUser = userService.selectUserById(id);
        ChatUserVo chatUserVo = new ChatUserVo();
        if (sysUser != null){
            chatUserVo.setId(sysUser.getUserId());
            chatUserVo.setDetail(sysUser.getRemark());
            chatUserVo.setHeadImg(sysUser.getAvatar());
            chatUserVo.setName(sysUser.getNickName());
        }
        return ResultVo.success(chatUserVo);

    }

//    Authentication是SpringSecurity提供的全局对象，用来获取登录成功的User，若没用到 SpringSecurity可删除此形参
//    @MessageMapping("/sendMsg")
//    public void handleMsg(@Payload ChatMsg chatMsg, @Header("Authorization") String token) {
//        // 通过SimipMessagingTemplate发送消息
//        // 访问已登录用户的信息
//
//        System.out.println(Thread.currentThread().getId());
//        Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
//        if (authentication == null && !StringUtils.isEmpty(token)){
//            token = token.replace("Bearer ","");
//            try {
//                LoginUser loginUser = tokenService.getLoginUserByToken(token);
//                //将拿到的登录用户信息,存入到ThreadLocal
//                if (StringUtils.isNotNull(loginUser)){
//                    UsernamePasswordAuthenticationToken authenticationToken = new UsernamePasswordAuthenticationToken(loginUser, null, loginUser.getAuthorities());
//                    SecurityContextHolder.getContext().setAuthentication(authenticationToken);
//                    //再取一次
//                    authentication = SecurityContextHolder.getContext().getAuthentication();
//                }
//            } catch (Exception e) {
//                e.printStackTrace();
//                throw e;
//            }
//        }
//        LoginUser loginUser = (LoginUser) authentication.getPrincipal();
//
//
//
//        chatMsg.setFrom(loginUser.getUserId());
//        //获取发送者的用户名
//        chatMsg.setFromNickName(loginUser.getUsername());
//
//        /**
//         * 点对点发送消息
//         * 1.消息接收者
//         * 2.消息队列
//         * 3.消息对象
//         * 消息的类型默认是/user，这个是websocket对单个客户端发送消息特殊的消息类型
//         */
//        log.info("用户[{}]发送消息=========={}", loginUser.getUsername(), chatMsg);
//        simpMessagingTemplate.convertAndSendToUser(chatMsg.getTo().toString(), "/queue/messages", chatMsg);
//    }


    @MessageMapping("/sendMsg")
    public void handleMsg(@Payload ChatMsg chatMsg,Principal principal) {
        // 通过SimipMessagingTemplate发送消息
        //获取发送者的唯一凭证
        chatMsg.setFrom(Long.valueOf(principal.getName()));
        /**
         * 点对点发送消息
         * 1.消息接收者
         * 2.消息队列
         * 3.消息对象
         * 消息的类型默认是/user，这个是websocket对单个客户端发送消息特殊的消息类型
         */
        log.info("用户[{}]发送消息=========={}", principal.getName(), chatMsg);
        simpMessagingTemplate.convertAndSendToUser(chatMsg.getTo().toString(), "/queue/messages", chatMsg);
    }

    /**
     * 一对一订阅通知
     */
//    @SubscribeMapping("/user/{userId}/queue/messages")
//    public ChatMsg subOnUser(@DestinationVariable String userId, StompHeaderAccessor stompHeaderAccessor, Principal principal) {
//        log.info(userId + "/queue/messages 已订阅");
//        return new ChatMsg("感谢你订阅了 一对一服务");
//    }



}
